package com.example.identifyvisio.utis;

import com.example.identifyvisio.constants.Constants;
import com.example.identifyvisio.model.component.CoordinatesAndParent;
import com.example.identifyvisio.model.component.Position;
import com.example.identifyvisio.model.component.Size;
import com.example.identifyvisio.model.node.*;
import com.example.identifyvisio.model.node.judge.Style;
import org.w3c.dom.Element;
import org.w3c.dom.Node;
import org.w3c.dom.NodeList;

import java.util.*;
import java.util.regex.Matcher;
import java.util.regex.Pattern;

/**
 * 各节点的值获取
 */

public class NodeValueUtil {
    /**
     * 节点的公共连接点获取
     *
     * @return
     */
    public static Ports getPorts() {
        Ports ports = new Ports();
        Groups groups = new Groups();
        Drop topGroups = new Drop();
        topGroups.setPosition("top");
        Attrs attrs = new Attrs();
        Circle circle = new Circle();
        circle.setR(4);
        circle.setMagnet(true);
        circle.setStroke("#2694fa");
        circle.setStrokeWidth(1);
        circle.setFill("#fff");
        circle.setStyle(new Style("hidden"));
        attrs.setCircle(circle);
        topGroups.setPosition("top");
        topGroups.setAttrs(attrs);
        groups.setTop(topGroups);

        Drop rightGroups = new Drop();
        rightGroups.setPosition("right");
        rightGroups.setAttrs(attrs);
        groups.setRight(rightGroups);

        Drop bottomGroups = new Drop();
        bottomGroups.setPosition("bottom");
        bottomGroups.setAttrs(attrs);
        groups.setBottom(bottomGroups);

        Drop leftGroups = new Drop();
        leftGroups.setPosition("left");
        leftGroups.setAttrs(attrs);
        groups.setLeft(leftGroups);

        ArrayList<Items> itemsArrayList = new ArrayList<>();
        Items top = new Items();
        top.setGroup("top");
        top.setId("port3");
        itemsArrayList.add(top);

        Items right = new Items();
        right.setGroup("right");
        right.setId("port2");
        itemsArrayList.add(right);

        Items bottom = new Items();
        bottom.setGroup("bottom");
        bottom.setId("port4");
        itemsArrayList.add(bottom);

        Items left = new Items();
        left.setGroup("left");
        left.setId("port1");
        itemsArrayList.add(left);

        ports.setGroups(groups);

        ports.setItems(itemsArrayList);
        return ports;
    }

    /**
     * 获取节点的坐标和父节点
     *
     * @param
     * @return
     */
    public static CoordinatesAndParent getObtainCoordinates(HashMap<Integer, Map<String, String>> dataMap,
                                                            Map<String, String> shapeMap, HashMap<String, List<Position>> positionMap) {
        CoordinatesAndParent coordinatesAndParent = new CoordinatesAndParent();
        //缩放倍率
        double x = 4;
        double y = 5;
        //获取该节点的父泳道坐标对象
        List<Position> positions = positionMap.get("0");
        if (shapeMap.get("relationships") == null) {
            Map<String, String> stringMap = dataMap.get(0);
            coordinatesAndParent.setParent(stringMap.get("UniqueID"));
        } else {
            //第一个是现左上角坐标，第二个是visio左上角坐标
            //通过关系id获取父泳道的坐标
            List<String> matches = getRelationship(shapeMap.get("relationships"));
            for (String match : matches) {
                if (dataMap.containsKey(Integer.valueOf(match))) {
                    Map<String, String> stringMap = dataMap.get(Integer.valueOf(match));
                    positions = positionMap.get(match);
                    //缩放倍率
                   x = positions.get(2).getX() > 2 ? positions.get(2).getX() - 1 : positions.get(2).getX();
                   y = positions.get(2).getY() > 2 ? positions.get(2).getY() - 1 : positions.get(2).getY();
                    coordinatesAndParent.setParent(stringMap.get("UniqueID"));
                }
            }
        }
        //获取本身节点的中心坐标，渲染到会话中设为左上角坐标的依据
        double primaryPinX = Double.parseDouble(shapeMap.get("PinX"));
        double primaryPinY = Double.parseDouble(shapeMap.get("PinY"));
        Size size = new Size(shapeMap.get("type"));
        if (shapeMap.containsKey("Width")) {
            double width = Double.parseDouble(shapeMap.get("Width"));
            primaryPinX = primaryPinX - (width / 2);
            size.setWidth(width * x);
        } else {
            double width = size.getWidth();
            primaryPinX = primaryPinX - (width / 2);
            size.setWidth(width * x);
        }
        if (shapeMap.containsKey("Height")) {
            double height = Double.parseDouble(shapeMap.get("Height"));
            primaryPinY = primaryPinY - (height / 2);
            size.setHeight(height * y);
        } else {
            double height = size.getHeight();
            primaryPinY = primaryPinY - (height / 2);
            size.setHeight(height * y);
        }
        //使用visio的坐标差 * 2 + 会话中泳道的X坐标，做为节点的坐标
        double pinX = (primaryPinX - positions.get(1).getX()) * x + positions.get(0).getX();
        double differ = (positions.get(1).getY() - primaryPinY) * y;
        //根据会话的Y轴，需要与visio的Y坐标反转：visio泳道Y + 高度差 - visio泳道Y坐标与-250坐标的高度差。
        double pinY = positions.get(1).getY() + differ - positions.get(0).getY();
        Position position = new Position(pinX, pinY);
        coordinatesAndParent.setPosition(position);
        coordinatesAndParent.setSize(size);
        return coordinatesAndParent;
    }

    /*
    连接线连接点
     */
    public static String getToPart(double pinX, double pinY, double x, double y) {
        if (Math.abs(pinX - x) < 2) {
            return pinY > y ? "port4" : "port3";
        }
        if (Math.abs(pinY - y) < 2) {
            return pinX > x ? "port1" : "port2";
        }
        return null;
    }

    /**
     * 获取Cell属性值
     *
     * @param shapeElement
     * @param cellName
     * @return
     */
    public static String getCellValue(Element shapeElement, String cellName) {
        NodeList cellNodes = shapeElement.getElementsByTagName("Cell");
        for (int j = 0; j < cellNodes.getLength(); j++) {
            Node cellNode = cellNodes.item(j);
            if (cellNode.getNodeType() == Node.ELEMENT_NODE) {
                Element cellElement = (Element) cellNode;
                if (cellElement.getAttribute("N").equals(cellName) && "Relationships".equals(cellName)) {
                    return cellElement.getAttribute("F");
                } else if (cellElement.getAttribute("N").equals(cellName)) {
                    return cellElement.getAttribute("V");
                }
            }
        }
        return null;
    }

    /**
     * 获取关系组件
     *
     * @param
     * @return
     */
    public static List<String> getRelationship(String relationships) {
        // 用于存储匹配结果的列表
        List<String> matches = new ArrayList<>();
        if (relationships == null ){
            matches.add(String.valueOf(0));
            return matches;
        }
        // 创建 Pattern 对象
        Pattern pattern = Pattern.compile(Constants.regex);
        Matcher matcher = pattern.matcher(relationships);

        while (matcher.find()) {
            matches.add(matcher.group().trim()); // trim() 去除首尾空白字符
        }
        return matches;
    }
}
